home *** CD-ROM | disk | FTP | other *** search
/ Celestin Apprentice 2 / Apprentice-Release2.iso / Source Code / C / Utilities / uupc 3.1 / (uupc π) / dcpxfer.c < prev    next >
Encoding:
C/C++ Source or Header  |  1994-03-22  |  17.1 KB  |  677 lines  |  [TEXT/KAHL]

  1. /*            dcpxfer.c
  2.  
  3.             Revised edition of dcp
  4.  
  5.             Stuart Lynne May/87
  6.  
  7.             Copyright (c) Richard H. Lamb 1985, 1986, 1987
  8.             Changes Copyright (c) Stuart Lynne 1987
  9.             Portions Copyright © David Platt, 1992, 1991.  All Rights Reserved
  10.             Worldwide.
  11.  
  12. */
  13. /* "DCP" a uucp clone. Copyright Richard H. Lamb 1985,1986,1987 */
  14. /* file send routines */
  15. #include "dcp.h"
  16. #include <unix.h>
  17. #include <ctype.h>
  18.  
  19. #include "dcpxfer.proto.h"
  20. static int getfile(void);
  21.  
  22. static unsigned char    rpacket[MAXPACK+4];
  23. static unsigned char    spacket[MAXPACK+4];
  24. static long                xtime, tsize;
  25. static char                id[20];
  26. static struct tm        *now;
  27. static int                reportRfileError;
  28. /**/
  29. /***************SEND PROTOCOL***************************/
  30. /*
  31.  *  s d a t a
  32.  *
  33.  *  Send File Data
  34.  */
  35. sdata(void)
  36. {
  37. int response;
  38.  
  39.     while( TRUE ) {
  40.  
  41.         if (response = ( *sendpkt) ( spacket, size, 0 ))
  42.             return (0 );     /* send data */
  43.         if ((size=bufill((char *)spacket)) == 0)  /* Get data from file */
  44.             return( 'Z' );                         /* If EOF set state to that */
  45.         tsize += (long)size;
  46.     }
  47. }
  48.  
  49.  
  50. /*
  51.  *  b u f i l l
  52.  *
  53.  *  Get a bufferful of data from the file that's being sent.
  54.  *  Only control-quoting is done; 8-bit & repeat count prefixes are
  55.  *  not handled.
  56.  */
  57. bufill(char *buffer)
  58. {
  59.     return( read(fp, buffer, pktsize) );/* Handle partial buffer */
  60. }
  61.  
  62.  
  63. /*
  64.  *  s b r e a k
  65.  *
  66.  *  Send Break (EOT)
  67.  */
  68. sbreak(void)
  69. {
  70.     int    len, i;
  71.     sprintf((char *)spacket, "H");
  72.     if ((*sendmsg)(spacket, FALSE))
  73.         return(0);
  74.     if ((*getmsg)(spacket, &len))
  75.         return(0);
  76.     printmsg( 2, "Switch modes" );
  77.     if (spacket[1] == 'N')
  78.         return('G');
  79.     return('Y');
  80. }
  81.  
  82.  
  83. /**/
  84. /*
  85.  *  s e o f
  86.  *
  87.  *  Send End-Of-File.
  88.  */
  89. seof(void)
  90. {
  91.     int    len, i;
  92.     long int ticks, bytes;
  93. /* send end-of-file indication, and perhaps receive a lower-layer ACK/NAK */
  94.     switch ((*eofpkt)()) {
  95.      case 'R':            /* retry */
  96.          printmsg(0, "Remote system asks that the file be resent");
  97.         lseek(fp, 0L, SEEK_SET);
  98.         size = bufill((char *)spacket);
  99.         tsize = (long)size;
  100.         (*filepkt)();                /* warmstart file-transfer protocol */
  101.          return 'D';                    /* stay in data phase */
  102.      case 'N':
  103.          return(0);                    /* cannot send file */
  104.      case 'Y':
  105.          break;                        /* sent, proceed */
  106.      case 'Q':
  107.          printmsg(0, "Remote gave up... try again later");
  108.         xfer_problems ++;
  109.          return 'A';
  110.     }
  111.     if((*getmsg)(rpacket, &len)) {
  112.         printmsg(0, "Never got yea/nay response at end-of-file");
  113.         xfer_problems ++;
  114.         return(0); /* didn't rec CY or CN packet */
  115.     }
  116.     if(strncmp((char *)rpacket, "CY", 2)) {
  117.         printmsg(0, "Remote had trouble with the file");
  118.         xfer_problems ++;
  119.         return(0); /* cant send file */
  120.     }
  121. #ifdef    THINK_C
  122.     xtime = TickCount() - xtime;
  123. #endif
  124.     close(fp);
  125.     fp = (-1);
  126.      importpath( hostfile, fromfile );
  127.     UNLINK(hostfile);
  128.     printmsg( 1, "Transfer of %s (%s) completed.", fromfile, hostfile);
  129. #ifdef    THINK_C
  130.     ticks = xtime ? xtime : 1;
  131.     bytes = remote_stats.bsent - remote_stats.bstart;
  132.     printmsg( 0, "Copy succeeded, %ld chars/sec", (bytes * 60) / ticks);
  133.     time(&theTime);
  134.     now = localtime(&theTime);
  135.     fprintf( syslog, "%s!%s (%d/%d-%02d:%02d:%02d) -> %ld / %0.2f secs\n",
  136.                      nodename, id,
  137.                      now->tm_mday, (now->tm_mon+1),
  138.                      now->tm_hour, now->tm_min, now->tm_sec, tsize, xtime/60.0 );
  139. #else
  140.     printmsg( 0, "Copy succeeded");
  141. #endif
  142.     return('F');                    /* go get the next file to send */
  143. }
  144.  
  145.  
  146. /**/
  147. /*
  148.  *  s f i l e
  149.  *
  150.  *  Send File Header.
  151.  */
  152. sfile(void)
  153. {
  154.     int    i, len, resp;
  155.     char * cp;
  156.     char tmpfilename[FILENAME_MAX];
  157.     if (fp == -1) {/* If not already open, */
  158. next:    printmsg( 3, "looking for next file..." );
  159.         if (getfile()) { /* get next file from current work*/
  160.             if (fw != (FILE *)NULL) {
  161.                 fclose(fw);
  162.                 fw = (FILE *)NULL;
  163.             }
  164.             UNLINK( cfile );/* close and delete completed workfile */
  165.             if (Main_State == Cancel_Call) {
  166.                 return ('H'); /* semi-polite disconnect */
  167.             }
  168.             return('B'); /* end sending session */
  169.         }
  170.  
  171.          importpath( hostfile, fromfile );
  172.  
  173.       if (*tofile == 'S')  {
  174.          printmsg(3, "Opening %s (%s) for sending.", fromfile, hostfile);
  175.         fp = OPEN (hostfile, 0);/* open the file to be sent */
  176.          if (fp == -1)
  177.          {
  178.              if (errno == ENOENT) {
  179.                  printmsg(0, "sfile: File %s (%s) does not exist, skipped", fromfile, hostfile);
  180.                  return 'F';
  181.              } else {
  182.                    printmsg(0, "sfile: Cannot open file %s (%s), error %d", fromfile, hostfile, errno);
  183.                 xfer_problems ++;
  184.                 return 'A';
  185.             }
  186.          } /* if */
  187.       } /* if */
  188. /*--------------------------------------------------------------------*/
  189. /*    If the target is a directory, automatically put a file into     */
  190. /*    it rather than on it!                                           */
  191. /*--------------------------------------------------------------------*/
  192.       else {
  193. #ifdef STAT
  194.          struct  stat    statbuf;
  195.  
  196.          if ((hostfile[strlen(hostfile) - 1] == '/') ||
  197.              ((stat(hostfile , &statbuf) == 0) &&
  198.               (statbuf.st_mode & S_IFDIR)))
  199.          {
  200.             char *slash = strrchr( rmtfname, '/');
  201.             if ( slash == NULL )
  202.                slash = rmtfname;
  203.             else
  204.                slash ++ ;
  205.             printmsg(3,"sfile: Destination \"%s\" is directory, appending filename \"%s\"", hostfile, slash);
  206.             if (hostfile[strlen(hostfile) - 1] != '/')
  207.                strcat(hostfile, "/");
  208.             strcat( hostfile, slash );
  209.          } /* if */
  210. #endif
  211.       } /* else */
  212.    } /* if */
  213.    else
  214.       return 'A'; /* Something's already open.  We're in trouble! */
  215.  
  216.     if (*tofile == 'S') {
  217.         printmsg( 1, "Sending %s (%s) to %s", fromfile, hostfile, rmtfname);
  218.         printmsg( 0, "Send %s -> %s", fromfile, rmtfname);
  219.     } else {
  220.         printmsg( 1, "Receiving %s (%s) from %s", fromfile, hostfile, rmtfname);
  221.         printmsg( 0, "Recv %s <- %s", fromfile, rmtfname);
  222.     }
  223.     xtime = TickCount();
  224.     remote_stats.bstart = remote_stats.bsent;
  225.    if ((*sendmsg)((char *) tofile, FALSE))
  226.            return 0;      /* send 'S fromfile tofile user - tofile 0666' */
  227.  
  228.    if ((*getmsg)((char *) spacket, &len))
  229.       return 0;
  230.  
  231.    if (spacket[1] != 'Y') {
  232.            if (spacket[0] == 'R') {
  233.                switch (spacket[2]) {
  234.                    case '2':
  235.                        printmsg(0, "Remote is not willing to send that file");
  236.                        break;
  237.                    case '6':
  238.                        printmsg(0, "Remote says the file is too big to send");
  239.                        break;
  240.                    default:
  241.                        printmsg(0, "Remote won't send file, didn't say why");
  242.                        break;
  243.                }
  244.                goto next;
  245.            } else {
  246.             xfer_problems ++;
  247.                switch (spacket[2]) {
  248.                    case '2':
  249.                        printmsg(0, "Cannot send; remote reports trouble with work files");
  250.                        break;
  251.                    case '4':
  252.                        printmsg(0, "Cannot send; remote has denied permission");
  253.                        break;
  254.                    default:
  255.                        printmsg(0, "Cannot send; remote didn't say why");
  256.                        break;
  257.                }
  258.             return 'A';    /* If other side says no, then quit */
  259.            }
  260.    }
  261.  
  262.    if (*tofile == 'S') {
  263.         size = bufill((char *)spacket);
  264.         tsize = (long)size;
  265.     }
  266.    else  {
  267.             /* Try to open a new file */
  268.         if ( strncmp( hostfile, "~/", 2 ) == SAME ) {
  269.             sprintf( tmpfilename, "%s%s", pubdir, hostfile+1);
  270.             fp = CREAT (tmpfilename, 0775, 'b');
  271.         } else {
  272.             fp = CREAT( hostfile, 0775, 'b' );
  273.         }
  274.         if (fp == -1) { 
  275.             printmsg( 0, "cannot create %s", tofile ); /* Give up if can't */
  276.             return('A');
  277.         }
  278.    }
  279.  
  280.     (*filepkt)(); /* warmstart file-transfer protocol */
  281.     return(char)(*tofile == 'S' ? 'D' : 'R');
  282.                               /* Is this how to do it ? */
  283.  
  284. }
  285.  
  286.  
  287. /**/
  288. /*
  289.  *  s i n i t
  290.  *
  291.  *  Send Initiate: send this host's parameters and get other side's back.
  292.  */
  293. sinit(void)
  294. {
  295.     if ((*openpk)(TRUE))
  296.         return('X');
  297.     return('B');
  298. }
  299.  
  300. /*
  301.    g e t f i l e
  302.  
  303.    Reads the next line from the presently open call file
  304.    (*workfile) and determines from this the next file to be sent
  305.    (*fromfile).  If there are no more, TRUE is returned.
  306. */
  307. static int getfile(void)
  308. {
  309.    char line[BUFSIZ];
  310.    char fname[FILENAME_MAX], tname[FILENAME_MAX], dname[FILENAME_MAX];
  311.    char type[5], who[20], flgs[16];
  312.    int i;
  313.  
  314.    if (fgets(line, BUFSIZ, fw) == (char *)NULL)
  315.       return TRUE;
  316.  
  317.    i = strlen(line) - 1;
  318.    if (line[i] == '\n')            /* remove new_line from card */
  319.       line[i] = '\0';
  320.  
  321.    sscanf(line, "%s %s %s %s %s %s", type, fname, tname, who, flgs, dname);
  322.  
  323.    strcpy(tofile, line);
  324.    if (*type == 'R')  {
  325.       del_file_flag = FALSE;        /* we aren't about to delete anything! */
  326.       strcpy(fromfile, tname);      /* NOTE - strange use of the name 'fromfile' */
  327.       strcpy( rmtfname, fname );    /* Save for sfile() magic  */
  328.    }
  329.    else if (strcmp(dname, "D.0") == 0)  {
  330.            del_file_flag = FALSE;
  331.            strcpy(fromfile, fname);
  332.            strcpy(rmtfname, tname);
  333.    }
  334.    else  {
  335.            del_file_flag = TRUE;
  336.            strcpy(fromfile, dname); /* correct name according to Nutshell */
  337.            strcpy(rmtfname, tname);
  338.    }
  339.  
  340.    printmsg(3, "getfile: fromfile=%s, tofile=%s.", fromfile, tofile);
  341.  
  342.    return FALSE;
  343.  
  344. } /*getfile*/
  345.  
  346.  
  347. /**/
  348. /*********************** MISC SUB SUB PROTOCOL *************************/
  349. /*
  350. **
  351. **schkdir
  352. ** scan the dir
  353. */
  354. schkdir(void)
  355. {
  356.     char    c;
  357.     c = scandir();
  358.     if (c == 'Q') {
  359.         return('Y');
  360.     }
  361.     if (c == 'S') {
  362.         sprintf((char *)rpacket, "HN");
  363.         if ((*sendmsg)(rpacket, FALSE))
  364.             return(0);
  365.     }
  366.     return('B');
  367. }
  368.  
  369.  
  370. /**/
  371. /*
  372.  *
  373.  *      endp() end protocol
  374.  *
  375. */
  376. endp(int polite)
  377. {
  378.     if (polite) {
  379.         sprintf((char *)rpacket, "HY");
  380.         (*sendmsg)(rpacket, TRUE); /* dont wait for ACK */
  381.         zzz(2);            /* allow peer a moment to hear msg before hangup occurs */
  382.     } else {
  383.         printmsg(0, "Closing connection (cancelled by user)");
  384.     }
  385.     (*closepk)();
  386.     printmsg( 0, "Conversation complete");
  387.     return('P');
  388. }
  389.  
  390.  
  391. /**/
  392. /***********************RECIEVE PROTOCOL**********************/
  393. /*
  394.  *  r d a t a
  395.  *
  396.  *  Receive Data
  397.  */
  398. rdata(void)
  399. {
  400.     int    len, wrote;
  401.     long int ticks, bytes;
  402.     int resp;
  403.     resp = (*getpkt)(rpacket, &len);
  404.     if (resp == 'R') { /* Retransmission required */
  405.         return resp;
  406.     }
  407.     if (resp != 0)
  408.         return(0);
  409.     if (len > 0) {
  410.         wrote = write(fp, (char *)rpacket, len);/* Write the data to the file */
  411.         tsize += (long)len;
  412.         if (len != wrote && !reportRfileError) {
  413.             printmsg( 0, "Write error, tried %d, wrote %d", len, wrote);
  414.             reportRfileError = 1;
  415.         }
  416.         return('D');/* Remain in data state */
  417.     }
  418.     if (len < 0) {
  419.         wrote = write(fp, (char *)rpacket, -len);/* Write the final data to the file */
  420.         tsize -= (long)len;
  421.         if (-len != wrote && !reportRfileError) {
  422.             printmsg( 0, "Write error, tried %d, wrote %d", -len, wrote);
  423.             reportRfileError = 1;
  424.         }
  425.     }
  426. #ifdef    THINK_C
  427.     xtime = TickCount() - xtime;
  428. #endif
  429.     close(fp);
  430.     fp = -1;
  431.     if ((*sendresp)(OK)) {
  432.         return (0);
  433.     }
  434.     if (reportRfileError) {
  435.         strcpy((char *)spacket, "CN5");
  436.     } else {
  437.         strcpy((char *)spacket, "CY");
  438.     }
  439.     if ((*sendmsg)(spacket, FALSE)) {
  440.         return (0);
  441.     }
  442.     ticks = xtime ? xtime : 1;
  443.     bytes = remote_stats.breceived - remote_stats.bstart;
  444.     if (reportRfileError) {
  445.         printmsg( 0, "Copy failed");
  446.         xfer_problems ++;
  447.     } else {
  448.         printmsg( 0, "Copy succeeded, %ld chars/sec", (bytes * 60) / ticks);
  449.     }
  450.     time(&theTime);
  451.     now = localtime(&theTime);
  452.     fprintf( syslog, "%s!%s (%d/%d-%02d:%02d:%02d) <- %ld / %0.2f secs\n",
  453.                      rmtname, id,
  454.                      now->tm_mday, (now->tm_mon+1),
  455.                      now->tm_hour, now->tm_min, now->tm_sec, tsize, xtime/60.0 );
  456.     return('F');
  457. }
  458.  
  459.  
  460. /*
  461.    r f i l e
  462.  
  463.    Receive File Header
  464. */
  465.  
  466. int rfile(void)
  467. {
  468.    char tmpfilename[FILENAME_MAX];
  469.    char buf[BUFSIZ];
  470.    char *flds[10], *cp;
  471.    int rx;                /* TRUE = Receive of file in progress  */
  472.    int nondefault;        /* TRUE = non default directory target */
  473.    int public;              /* TRUE = destined for public folder   */
  474.    int numflds;
  475.  
  476.    FILE *stream;
  477.  
  478.    printmsg(3, "rfile: entered");
  479.  
  480.    if (Main_State == Cancel_Call) {
  481.       return ('H');
  482.    }
  483.    
  484.    reportRfileError = 0;
  485.  
  486.    for (cp = buf; ; ) {
  487.       int len;
  488.       if ((*getmsg)((char *) rpacket, &len))
  489.          return 0;
  490.       memcpy(cp, (char *) rpacket, len);
  491.       cp += len;
  492.       if (cp[-1] == '\0')
  493.          break;
  494.    }
  495.  
  496. /*--------------------------------------------------------------------*/
  497. /*        Return if the remote system has no more data for us         */
  498. /*--------------------------------------------------------------------*/
  499.  
  500.    if ((buf[0] & 0x7f) == 'H')
  501.       return 'C';    /* the other side (master) is done */
  502.  
  503. /*--------------------------------------------------------------------*/
  504. /*                  Begin transforming the file name                  */
  505. /*--------------------------------------------------------------------*/
  506.  
  507.    printmsg(3, "rfile: command \"%s\"", buf);
  508.  
  509.    numflds = getargs( buf, flds );
  510.  
  511.    rx = (*flds[0] == 'S');         /* flag we are receiving a file */
  512.  
  513.    if (rx)
  514.       cp = flds[2];
  515.    else
  516.       cp = flds[1];
  517.  
  518.    nondefault = (strchr(cp , '/') != NULL) || (strchr(cp , '\\') != NULL);
  519.    strcpy(tmpfilename,cp);
  520.  
  521.     if ( strncmp( cp, "~/", 2 ) == SAME ) {
  522.         sprintf( tmpfilename, "%s%s", pubdir, cp+1);
  523.         public = 1;
  524.     } else {
  525.         strcpy( tmpfilename, cp );
  526.         public = 0;
  527.     }
  528.    printmsg(3, "rfile: destination \"%s\"", cp);
  529.  
  530. /*--------------------------------------------------------------------*/
  531. /* If the name has a path and we don't allow it, reject the transfer  */
  532. /*--------------------------------------------------------------------*/
  533.  
  534.    if (nondefault && ! public) 
  535.    {
  536.         if (rx) {
  537.             printmsg(0,"File %s not destined for spool directory, rejected.", cp);
  538.             sprintf((char *)rpacket, "SN2");
  539.         } else {
  540.             printmsg(0,"File %s not in spool directory, will not be sent", cp);
  541.             sprintf((char *)rpacket, "RN2");
  542.         }
  543.         if ((*sendmsg)(rpacket, FALSE))
  544.             return(0);
  545.         return 'F'; /* Reject this one but keep going */
  546.    }
  547.  
  548. /*--------------------------------------------------------------------*/
  549. /*       Check if the name is a directory name (end with a '/')       */
  550. /*--------------------------------------------------------------------*/
  551.  
  552. #ifdef STAT
  553.    if (rx && ((cp[strlen(cp) - 1] == '/') ||
  554.               ((stat(fromfile , &statbuf) == 0) &&
  555.                (statbuf.st_mode & S_IFDIR))))
  556. #else
  557.    if (rx && ((cp[strlen(cp) - 1] == '/')))
  558. #endif
  559.    {
  560.       printmsg(3, "rfile: destination is directory \"%s\"", flds[1]);
  561.       if ((cp = strrchr(flds[1], '/')) == NULL)
  562.          cp = flds[1];
  563.       else
  564.          cp++;
  565.       printmsg(3, "rfile: directory only, adding \"%s\"", cp);
  566.  
  567.       if ( tmpfilename[ strlen( tmpfilename ) - 1 ] != '/')
  568.          strcat(tmpfilename, "/");
  569.       strcat(tmpfilename, cp);
  570.    } /* if */
  571.  
  572.    if (rx)
  573.       printmsg(3, "rfile: receive file \"%s\"", tmpfilename);
  574.  
  575. /*--------------------------------------------------------------------*/
  576. /*          Let host munge filename as appropriate                    */
  577. /*--------------------------------------------------------------------*/
  578.  
  579. #ifdef IMPORTREMOTE
  580.    importpath(tofile, tmpfilename, rmtname);
  581. #else
  582.    importpath(tofile, tmpfilename);
  583. #endif
  584.  
  585.    printmsg(3, "rfile: host file \"%s\"", tofile);
  586.  
  587. /*--------------------------------------------------------------------*/
  588. /*       Don't allow files to be overlaid                             */
  589. /*--------------------------------------------------------------------*/
  590.  
  591.    if (rx && nondefault)
  592.    {
  593.       stream = fopen(tofile, "r");  /* Determine if the file exists
  594.                                        by opening it for input       */
  595.       if ( stream != NULL )         /* Does it exist?                */
  596.       {
  597.         fclose(stream);
  598.         printmsg(0, "rfile: Cannot receive \"%s\", \"%s\" exists",
  599.                      flds[1], tofile);
  600.         sprintf((char *)rpacket, "SN4");
  601.         if ((*sendmsg)(rpacket, FALSE))
  602.             return(0);
  603.         return 'F'; /* Reject this one but keep going */
  604.       }
  605.    } /* if rx */
  606.  
  607. /*--------------------------------------------------------------------*/
  608. /*            The filename is transformed, try to open it             */
  609. /*--------------------------------------------------------------------*/
  610.  
  611.    if (rx)
  612.    {
  613.         fp = CREAT( tofile, 0775, 'b' );
  614.  
  615.         if (fp == -1){
  616.             printmsg(0, "rfile: cannot open file %s (%s), error %d.",
  617.                         tmpfilename, tofile, errno);
  618.             sprintf((char *)rpacket, "SN4");
  619.             if ((*sendmsg)(rpacket, FALSE))
  620.                 return(0);
  621.             return 'F'; /* Reject this one but keep going */
  622.         } /* if */
  623.  
  624.         printmsg( 0, "Rcve %s <- %s", tofile, flds[1] );
  625.         remote_stats.bstart = remote_stats.breceived;
  626.         sprintf((char *)rpacket, "SY");
  627.         xtime = TickCount();
  628.         tsize = 0L;
  629.         strcpy(id, flds[3]);
  630.         if ((*sendmsg)(rpacket, FALSE))
  631.             return(0);
  632.         (*filepkt)(); /* init for file transfer */
  633.         return('D'); /* Switch to data state */
  634.    } /* if rx */
  635.    else
  636.    {
  637.       printmsg(3, "Opening %s (%s) for sending.", flds[1], tofile);
  638.         fp = OPEN(tofile, 0);/* open the file to be sent */
  639.         if (fp == -1) {/* If bad file pointer, give up */
  640.          printmsg(0, "rfile: Cannot open file %s (%s), error %d.", flds[1], tofile, errno);
  641.         sprintf((char *)rpacket, "RN2");
  642.         if ((*sendmsg)(rpacket, FALSE))
  643.             return(0);
  644.         return 'F'; /* Reject this one but keep going */
  645.       } /* if */
  646.  
  647.       strcpy( (char *) rpacket, "RY");
  648.       if ((*sendmsg)((char *) rpacket, FALSE))
  649.          return 0;
  650.       printmsg( 1, "Sending %s (%s) as %s", flds[1], hostfile, tofile);
  651.       printmsg( 0, "Send %s -> %s", flds[1], tofile);
  652.       size = bufill((char *)spacket);
  653.       tsize = (long)size;
  654.       (*filepkt)(); /* init for file transfer */
  655.       return 'S';     /* Switch to send data state */
  656.    } /* else */
  657.  
  658. } /*rfile*/
  659.  
  660.  
  661. /**/
  662. /*
  663.  *  r i n i t
  664.  *
  665.  *  Receive Initialization
  666.  */
  667. rinit(void)
  668. {
  669.     if ((*openpk)(FALSE))
  670.         return(0);
  671.     return('F');
  672. }
  673.  
  674.  
  675.  
  676.  
  677.